"use strict";

var _interopRequireDefault = require("@babel/runtime-corejs3/helpers/interopRequireDefault");

var _reverse = _interopRequireDefault(require("@babel/runtime-corejs3/core-js-stable/instance/reverse"));

/**
 * 查找满足条件的父节点
 *
 * @since 0.0.5
 * @category 树算法
 * @param {array} treeList 树形结构集合.
 * @param {any|function} param 唯一key或者校验函数.
 * @param {object} config 配置参数.
 * @param {boolean} config.props 属性配置
 * @param {string} config.props.prop 数据的唯一主键key, 默认: id.
 * @param {string} config.props.childrenProp 数据的子主键key, 默认: children.
 * @param {boolean} config.isAll 所有父节点, 默认false 返回节点对象; 为true时返回包含所有父节点的数组
 * @returns { object|array } 查找到的节点/节点数组
 *
 * @example
 *
 * z.treeFindParentNode([{ id: 1, children: [{ id: 3, parentId: 1 , children: [{ id: 4, parentId: 3 }]}] }, { id: 2 }], 4)
 * // => { id: 3, parentId: '1', children: [ { id: 4, parentId: 3 } ] }
 *
 * z.treeFindParentNode([{ id: 1, children: [{ id: 3, parentId: 1 , children: [{ id: 4, parentId: 3 }]}] }, { id: 2 }], node => node.id === 4)
 * // => { id: 3, parentId: '1', children: [ { id: 4, parentId: 3 } ] }
 *
 * z.treeFindParentNode([{ code: 1, list: [{ code: 3, pCode: 1 , list: [{ code: 4, pCode: 3 }]}] }, { code: 2 }], 4, { props: { prop: 'code', childrenProp: 'list' }, isAll: true })
 * // => [ { code: 1, list: [{ code: 3, pCode: 1 , list: [{ code: 4, pCode: 3 }]}] }, { code: 3, pCode: 1, list: [ { code: 4, pCode: 3 } ] } ]
 *
 * z.treeFindParentNode([{ code: 1, list: [{ code: 3, pCode: 1 , list: [{ code: 4, pCode: 3 }]}] }, { code: 2 }], node => node.code === 4, { props: { prop: 'code', childrenProp: 'list' }, isAll: true })
 * // => [ { code: 1, list: [{ code: 3, pCode: 1 , list: [{ code: 4, pCode: 3 }]}] }, { code: 3, pCode: 1, list: [ { code: 4, pCode: 3 } ] } ]
 *
 */
function treeFindParentNode(treeList, param) {
  var _ref = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {},
      _ref$props = _ref.props;

  _ref$props = _ref$props === void 0 ? {} : _ref$props;
  var _ref$props$prop = _ref$props.prop,
      prop = _ref$props$prop === void 0 ? 'id' : _ref$props$prop,
      _ref$props$childrenPr = _ref$props.childrenProp,
      childrenProp = _ref$props$childrenPr === void 0 ? 'children' : _ref$props$childrenPr,
      _ref$isAll = _ref.isAll,
      isAll = _ref$isAll === void 0 ? false : _ref$isAll;
  var callback = param;

  if (typeof callback !== 'function') {
    callback = function callback(node) {
      return node[prop] === param;
    };
  }

  var func = function func(array, parentNode) {
    for (var i = 0; i < array.length; i++) {
      var item = array[i];

      var _rt = callback(item);

      if (_rt) return parentNode;

      if (item[childrenProp]) {
        var _rt2 = func(item[childrenProp], item);

        if (_rt2) return _rt2;
      }
    }
  };

  var rt = [];

  var _loop = function _loop() {
    var node = func(treeList, undefined);

    if (node) {
      rt.push(node);

      callback = function callback(n) {
        return n[prop] === node[prop];
      };
    } else {
      callback = undefined;
    }
  };

  while (callback) {
    _loop();
  }

  return isAll ? (0, _reverse.default)(rt).call(rt) : rt.shift();
}

module.exports = treeFindParentNode;